package com.zt.questionnaire.common.typehandler;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.parser.Feature;
import org.apache.ibatis.type.BaseTypeHandler;
import org.apache.ibatis.type.JdbcType;

import java.sql.CallableStatement;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Map;

/**
 * 如果含有Float类型，使用Double
 * @author funnywus
 */
public class EntityJsonMapTypeHandler extends BaseTypeHandler<Map> {

	private String toJson(Map map) {
		try {
			return JSON.toJSONString(map);
		} catch (Exception e) {
			throw new RuntimeException(e);
		}
	}

	private Map toObject(String content) {
		if (content != null && !content.isEmpty()) {
			try {
				/**
				 * fastjson缺省反序列化带小数点的数值类型为BigDecimal，因为在真实的业务中，float/double表示的二进制精度和直观理解的十进制精度不太一样。
				 * 但还是存在使用float/double而不是BigDecimal的场景。
				 * https://github.com/alibaba/fastjson/wiki/deserialize_disable_bigdecimal_cn
				 */
				int disableDecimalFeature = JSON.DEFAULT_PARSER_FEATURE & ~Feature.UseBigDecimal.getMask();
				return JSON.parseObject(content, Map.class, disableDecimalFeature);
			} catch (Exception e) {
				throw new RuntimeException(e);
			}
		} else {
			return null;
		}
	}

	@Override
	public Map getNullableResult(ResultSet rs, String paramString) throws SQLException {
		//查询是起作用
		return this.toObject(rs.getString(paramString));
	}

	@Override
	public Map getNullableResult(ResultSet rs, int paramInt) throws SQLException {
		return this.toObject(rs.getString(paramInt));
	}

	@Override
	public Map getNullableResult(CallableStatement cs, int paramInt) throws SQLException {
		return this.toObject(cs.getString(paramInt));
	}

	@Override
	public void setNonNullParameter(PreparedStatement ps, int paramInt, Map paramT,
			JdbcType paramJdbcType) throws SQLException {
		//insert时起作用
		ps.setString(paramInt, this.toJson(paramT));
	}
}
